package cn.org.donald.framework.authentication.realm;

import cn.org.donald.framework.service.impl.SysPermissionServiceImpl;
import cn.org.donald.framework.service.impl.SysRoleServiceImpl;
import cn.org.donald.framework.service.impl.SysUserServiceImpl;
import cn.org.donald.framework.authentication.salt.MyByteSource;
import cn.org.donald.pojo.entity.Permission;
import cn.org.donald.pojo.entity.Role;
import cn.org.donald.pojo.entity.User;
import cn.org.donald.framework.util.ApplicationContextUtil;
import org.apache.shiro.authc.*;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.util.ObjectUtils;

import java.util.List;

/**
 * @author ： Donald
 * @date ： 2020/10/16 22:28
 * @description： 自定义realm
 */
public class CustomerRealm extends AuthorizingRealm {

    private Logger logger = LoggerFactory.getLogger(CustomerRealm.class);


    /**
     * 权限认证
     * @param principalCollection
     * @return
     */
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principalCollection) {
        logger.info(">>>访问鉴权<<<");
        try {
            //获取主身份信息
            String primaryPrincipal = (String) principalCollection.getPrimaryPrincipal();
            //因为是有jwt存者用户信息,所有这里获取用户名是从jwt获取

            /*根据主身份信息获取角色和权限*/
            //去bean工厂获取server的bean
            SysUserServiceImpl sysUserService = (SysUserServiceImpl) ApplicationContextUtil.getBean("sysUserServiceImpl");
            SysRoleServiceImpl sysRoleService = (SysRoleServiceImpl) ApplicationContextUtil.getBean("sysRoleServiceImpl");
            SysPermissionServiceImpl sysPermission = (SysPermissionServiceImpl) ApplicationContextUtil.getBean("sysPermission");

            User user = sysUserService.findByUserName(primaryPrincipal);
            List<Role> roles = sysRoleService.findByUserId(user.getId());
            //给鉴权构造赋值角色和权限
            if(!roles.isEmpty()){
                SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();
                roles.forEach(role -> {
                    //添加角色
                    info.addRole(role.getRoleName());

                    //添加对应权限
                    List<Permission> permissions = sysPermission.findByRoleId(role.getId());
                    permissions.forEach(permission -> info.addStringPermission(permission.getPermissionName()));

                });
                return info;
            }
        }catch (Exception e){
            throw new NullPointerException("访问权限不足");
        }


        return null;
    }

    /**
     * 登录认证
     * @param authenticationToken
     * @return
     * @throws AuthenticationException
     */
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
        String principal = (String) authenticationToken.getPrincipal();

        //获取userServiceImpl的bean
        SysUserServiceImpl  sysUserService = (SysUserServiceImpl) ApplicationContextUtil.getBean("sysUserServiceImpl");

        //获取数据库用户信息
        User user = sysUserService.findByUserName(principal);

        if (ObjectUtils.isEmpty(user)){
            throw new UnknownAccountException();
        }

        return new SimpleAuthenticationInfo(user.getUserName(),
                user.getPassword(),
                MyByteSource.Util.bytes(user.getSaltValue()),//主要修改了这里
                this.getName());
    }
}
